package com.gxar.quick.ar.server.db.service;

import com.github.pagehelper.PageHelper;
import com.gxar.common.entity.Result;
import com.gxar.common.entity.SlippageResult;
import com.gxar.common.entity.login.UserProfile;
import com.gxar.common.exception.APIRuntimeException;
import com.gxar.common.utils.SnowFlakeUtils;
import com.gxar.fusion.redis.service.RedisService;
import com.gxar.quick.ar.server.base.common.constant.RedisConstant;
import com.gxar.quick.ar.server.base.common.constant.WorksConstant;
import com.gxar.quick.ar.server.base.common.enums.DeletedEnum;
import com.gxar.quick.ar.server.base.model.ResultCodeEnum;
import com.gxar.quick.ar.server.base.model.works.mapper.WorksDraftMapStruct;
import com.gxar.quick.ar.server.base.model.works.vo.request.WorksDraftUpdateRequest;
import com.gxar.quick.ar.server.base.model.works.vo.response.WorksDraftInfoResponse;
import com.gxar.quick.ar.server.base.model.works.vo.response.WorksDraftListResponse;
import com.gxar.quick.ar.server.base.model.works.vo.response.WorksDraftUpdateResponse;
import com.gxar.quick.ar.server.db.mapper.WorksDraftMapper;
import com.gxar.quick.ar.server.db.model.WorksDraftEntity;
import com.gxar.quick.ar.server.db.model.WorksEntity;
import com.gxar.quick.ar.server.db.repository.WorksDraftRepository;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.apache.dubbo.common.utils.CollectionUtils;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.text.SimpleDateFormat;
import java.util.Collections;
import java.util.Date;
import java.util.List;
import java.util.Optional;
import java.util.stream.Collectors;

/**
 * @author linsy
 * @version 1.0
 * @created 2023/11/13 11:21
 */
@Slf4j
@Service
@RequiredArgsConstructor
public class WorkDraftService {

    private final WorksDraftMapper worksDraftMapper;
    private final WorksDraftRepository worksDraftRepository;
    private final RedisService redisService;

    /**
     * 查看草稿详情
     *
     * @param userProfile 用户信息
     * @param id          草稿id
     * @return 草稿详情
     */
    public Result<WorksDraftInfoResponse> getDraftDetail(UserProfile userProfile, Long id) {
        Optional<WorksDraftEntity> worksDraftEntityOptional = worksDraftRepository.findById(id);
        if (worksDraftEntityOptional.isPresent()) {
            WorksDraftEntity worksDraftEntity = worksDraftEntityOptional.get();
            if (worksDraftEntity.getUserId().equals(userProfile.getId())
                    && DeletedEnum.FALSE.getCode().equals(worksDraftEntity.getDeleted())) {
                WorksDraftInfoResponse worksDraftInfoResponse = WorksDraftMapStruct.INSTANCE.entityToInfoResponse(worksDraftEntity);
                return Result.success(worksDraftInfoResponse);
            }
        }
        return Result.error(ResultCodeEnum.WORK_DRAFTS_NOT_EXIST);
    }

    /**
     * 作品草稿列表查询
     *
     * @param userProfile 用户信息
     * @param nextId      下一个请求id
     * @return 响应
     */
    public SlippageResult<WorksDraftListResponse> draftList(UserProfile userProfile, String nextId) {
        int pageNumber = 1;
        if (StringUtils.isNotBlank(nextId)) {
            String pageKey = String.format(RedisConstant.WORKS_DRAFT_PAGE_KEY, userProfile.getId(), nextId);
            Object pageInfo = redisService.get(pageKey);
            if (pageInfo != null) {
                pageNumber = Integer.parseInt(pageInfo.toString());
                redisService.remove(pageKey);
            }
        }
        PageHelper.startPage(pageNumber, WorksConstant.DEFAULT_QUERY_LIMIT);
        List<WorksDraftEntity> worksDraftEntities = worksDraftMapper.queryPage(userProfile.getId());
        if (CollectionUtils.isEmpty(worksDraftEntities)) {
            return SlippageResult.build(null, Collections.emptyList());
        }
        List<WorksDraftListResponse> response = WorksDraftMapStruct.INSTANCE.entityToListResponses(worksDraftEntities);
        for (WorksDraftListResponse listResponse : response) {
            SimpleDateFormat simpleDateFormat = new SimpleDateFormat("MM-dd");
            String dateFormat = simpleDateFormat.format(listResponse.getCreatedAt());
            String numberFormat = String.format("%02d", response.indexOf(listResponse) + 1);
            listResponse.setTag(dateFormat + "-" + numberFormat);
        }
        String nextedId = SnowFlakeUtils.getInstance().nextId();
        String pageKey = String.format(RedisConstant.WORKS_DRAFT_PAGE_KEY, userProfile.getId(), nextedId);
        redisService.set(pageKey, pageNumber + 1);
        redisService.expire(pageKey, RedisConstant.DEFAULT_EXPIRE_SECONDS);
        return SlippageResult.build(nextedId, response);
    }

    /**
     * 更新草稿
     *
     * @param userProfile             用户信息
     * @param id                      id
     * @param worksDraftUpdateRequest 请求
     * @return 响应
     */
    public Result<WorksDraftUpdateResponse> updateDraft(UserProfile userProfile, Long id, WorksDraftUpdateRequest worksDraftUpdateRequest) {
        Optional<WorksDraftEntity> worksDraftEntityOptional = worksDraftRepository.findById(id);
        if (worksDraftEntityOptional.isPresent()) {
            WorksDraftEntity worksDraftEntity = worksDraftEntityOptional.get();
            if (!worksDraftEntity.getUserId().equals(userProfile.getId())
                    || DeletedEnum.TRUE.getCode().equals(worksDraftEntity.getDeleted())) {
                throw new APIRuntimeException(ResultCodeEnum.WORK_DRAFTS_NOT_EXIST);
            }
            worksDraftEntity.setName(worksDraftUpdateRequest.getName());
            worksDraftEntity.setCoverPage(worksDraftUpdateRequest.getCoverPage());
            worksDraftEntity.setIdentify(worksDraftUpdateRequest.getIdentify());
            worksDraftEntity.setContent(worksDraftUpdateRequest.getContent());
            worksDraftEntity.setUpdatedAt(new Date());
            worksDraftEntity.setOperator(userProfile.getMobile());
            WorksDraftEntity updated = worksDraftRepository.save(worksDraftEntity);
            WorksDraftUpdateResponse response = WorksDraftMapStruct.INSTANCE.entityToUpdateResponse(updated);
            return Result.success(response);
        }
        return Result.error(ResultCodeEnum.WORK_DRAFTS_NOT_EXIST);
    }

    /**
     * 删除草稿作品
     *
     * @param userProfile 用户信息
     * @param id          草稿id
     * @return 是否删除
     */
    public Result<Boolean> deleteDraft(UserProfile userProfile, Long id) {
        Optional<WorksDraftEntity> worksDraftEntityOptional = worksDraftRepository.findById(id);
        if (worksDraftEntityOptional.isPresent()) {
            WorksDraftEntity worksDraftEntity = worksDraftEntityOptional.get();
            if (!worksDraftEntity.getUserId().equals(userProfile.getId())
                    || DeletedEnum.TRUE.getCode().equals(worksDraftEntity.getDeleted())) {
                throw new APIRuntimeException(ResultCodeEnum.WORK_DRAFTS_NOT_EXIST);
            }
            worksDraftEntity.setDeleted(DeletedEnum.TRUE.getCode());
            worksDraftEntity.setUpdatedAt(new Date());
            worksDraftRepository.save(worksDraftEntity);
        }
        return Result.success(true);
    }

    /**
     * 批量删除草稿作品
     *
     * @param userProfile 用户
     * @param ids         草稿作品id
     * @return 是否删除
     */
    @Transactional(rollbackFor = Throwable.class)
    public Result<Boolean> batchDeleteWorks(UserProfile userProfile, List<Long> ids) {
        List<WorksDraftEntity> worksDraftEntities = worksDraftRepository.findAllById(ids);
        List<WorksDraftEntity> worksDraftEntityList = worksDraftEntities.stream().filter(e -> e.getUserId().equals(userProfile.getId())).collect(Collectors.toList());
        if (ids.size() != worksDraftEntityList.size()) {
            throw new APIRuntimeException(ResultCodeEnum.DELETE_WORK_NOT_SELF);
        }
        worksDraftMapper.deleteByWorksId(ids);
        return Result.success(true);
    }

}
